package org.gd.hellojaxb.adapters;

import javax.xml.bind.annotation.adapters.XmlAdapter;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Locale;

public class DateAdaptersFactory {

    private static final Locale LOCALE = new Locale("UA");

    private static final SimpleDateFormat TIMESTAMP_FORMAT;
    private static final SimpleDateFormat DATE_TIME_FORMAT;
    private static final SimpleDateFormat DATE_FORMAT;
    private static final SimpleDateFormat TIME_FORMAT;
    private static final SimpleDateFormat SESSION_FORMAT;
    private static final SimpleDateFormat STATEMENTS_DATE_FORMAT;
    private static final SimpleDateFormat EDIT_PAY_DATE_FORMAT;
    private static final SimpleDateFormat MOBILE_PAY_DATE_FORMAT;

    static {
        TIMESTAMP_FORMAT = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSS", LOCALE);
        DATE_TIME_FORMAT = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss", LOCALE);
        DATE_FORMAT =      new SimpleDateFormat("yyyy-MM-dd", LOCALE);
        TIME_FORMAT =      new SimpleDateFormat("HH:mm:ss", LOCALE);
        SESSION_FORMAT =   new SimpleDateFormat("mm:ss", LOCALE);
        STATEMENTS_DATE_FORMAT = new SimpleDateFormat("dd.MM.yyyy", LOCALE);
        EDIT_PAY_DATE_FORMAT = new SimpleDateFormat("yyyy.MM.dd", LOCALE);
        MOBILE_PAY_DATE_FORMAT = new SimpleDateFormat("MM.dd.yyyy HH:mm:ss", LOCALE);
    }

    public static SimpleDateFormat getTimestampFormat() {
        return TIMESTAMP_FORMAT;
    }

    public static SimpleDateFormat getDateTimeFormat() {
        return DATE_TIME_FORMAT;
    }

    public static SimpleDateFormat getDateFormat() {
        return DATE_FORMAT;
    }

    public static SimpleDateFormat getTimeFormat() {
        return TIME_FORMAT;
    }

    public static SimpleDateFormat getSessionFormat() {
        return SESSION_FORMAT;
    }

    public static SimpleDateFormat getStatementsDateFormat() {
        return STATEMENTS_DATE_FORMAT;
    }

    public static SimpleDateFormat getEditPayDateFormat() {
        return EDIT_PAY_DATE_FORMAT;
    }

    public static SimpleDateFormat getMobilePayDateFormat() {
        return MOBILE_PAY_DATE_FORMAT;
    }

    private DateAdaptersFactory() {

    }

    public static final class Timestamp extends XmlAdapter<String, Date> {
        @Override
        public Date unmarshal(String v) throws Exception {
            if(v == null) {
                return null;
            }
            return getTimestampFormat().parse(v);
        }
        @Override
        public String marshal(Date v) throws Exception {
            if(v == null) {
                return null;
            }
            return getTimestampFormat().format(v);
        }
    }

    public static final class DateTimeFormat extends XmlAdapter<String, Date> {
        @Override
        public Date unmarshal(String v) throws Exception {
            if(v == null) {
                return null;
            }
            return getDateTimeFormat().parse(v);
        }
        @Override
        public String marshal(Date v) throws Exception {
            if(v == null) {
                return null;
            }
            return getDateTimeFormat().format(v);
        }
    }

    public static final class DateFormat extends XmlAdapter<String, Date> {
        @Override
        public Date unmarshal(String v) throws Exception {
            if(v == null) {
                return null;
            }
            return getDateFormat().parse(v);
        }
        @Override
        public String marshal(Date v) throws Exception {
            if(v == null) {
                return null;
            }
            return getDateFormat().format(v);
        }
    }

    public static final class TimeFormat extends XmlAdapter<String, Date> {
        @Override
        public Date unmarshal(String v) throws Exception {
            if(v == null) {
                return null;
            }
            return getTimeFormat().parse(v);
        }
        @Override
        public String marshal(Date v) throws Exception {
            if(v == null) {
                return null;
            }
            return getTimeFormat().format(v);
        }
    }

    public static final class SessionFormat extends XmlAdapter<String, Date> {
        @Override
        public Date unmarshal(String v) throws Exception {
            if(v == null) {
                return null;
            }
            return getSessionFormat().parse(v);
        }
        @Override
        public String marshal(Date v) throws Exception {
            if(v == null) {
                return null;
            }
            return getSessionFormat().format(v);
        }
    }

    public static final class StatementsDateFormat extends XmlAdapter<String, Date> {
        @Override
        public Date unmarshal(String v) throws Exception {
            if(v == null) {
                return null;
            }
            return getStatementsDateFormat().parse(v);
        }
        @Override
        public String marshal(Date v) throws Exception {
            if(v == null) {
                return null;
            }
            return getStatementsDateFormat().format(v);
        }
    }

    public static final class EditRegularPayDateFormat extends XmlAdapter<String, Date> {
        @Override
        public Date unmarshal(String v) throws Exception {
            if(v == null) {
                return null;
            }
            return getEditPayDateFormat().parse(v);
        }
        @Override
        public String marshal(Date v) throws Exception {
            if(v == null) {
                return null;
            }
            return getEditPayDateFormat().format(v);
        }
    }

    public static final class MobilePayDateFormat extends XmlAdapter<String, Date> {
        @Override
        public Date unmarshal(String v) throws Exception {
            if(v == null) {
                return null;
            }
            return getMobilePayDateFormat().parse(v);
        }
        @Override
        public String marshal(Date v) throws Exception {
            if(v == null) {
                return null;
            }
            return getMobilePayDateFormat().format(v);
        }
    }
}